#pragma once
#include <spdlog/spdlog.h>
#include <spdlog/sinks/stdout_color_sinks.h>
#include <spdlog/sinks/basic_file_sink.h>
#include <spdlog/async.h>
// spdlog::level::level_enum
namespace XKL
{
    std::shared_ptr<spdlog::logger> g_logger;

    void initLogger(const std::string& logger_name, 
    const std::string& logger_file, int logger_level, const int& thread_count = 1)
    {
        spdlog::flush_on((spdlog::level::level_enum)logger_level);
        spdlog::init_thread_pool(32768, thread_count);
        if(logger_name == "stdout")
            g_logger = spdlog::stdout_color_mt(logger_name);
        else
            g_logger = spdlog::basic_logger_mt<spdlog::async_factory>(logger_name, logger_file);
        g_logger->set_level((spdlog::level::level_enum)logger_level);
        g_logger->set_pattern("%H:%M:%S [%n][%-7l]%v");
    }
}

#define LOG_TRACE(format, ...) XKL::g_logger->trace(std::string("[{}:{}] ") + format, __FILE__, __LINE__, ##__VA_ARGS__)
#define LOG_DEBUG(format, ...) XKL::g_logger->debug(std::string("[{}:{}] ") + format, __FILE__, __LINE__, ##__VA_ARGS__)
#define LOG_INFO(format, ...) XKL::g_logger->info(std::string("[{}:{}] ") + format, __FILE__, __LINE__, ##__VA_ARGS__)
#define LOG_WARN(format, ...) XKL::g_logger->warn(std::string("[{}:{}] ") + format, __FILE__, __LINE__, ##__VA_ARGS__)
#define LOG_ERROR(format, ...) XKL::g_logger->error(std::string("[{}:{}] ") + format, __FILE__, __LINE__, ##__VA_ARGS__)
#define LOG_FATAL(format, ...) XKL::g_logger->critical(std::string("[{}:{}] ") + format, __FILE__, __LINE__, ##__VA_ARGS__)